import React, { Fragment, useCallback, useMemo } from 'react';

interface IImages {
    id: string | number;
    src: string;
    alt?: string;
    [propName: string]: any;
}

/**
 * @description 图片懒加载的自定义hook
 * @param {IImages[]} imgs 懒加载的图片数组
 * @param {React.CSSProperties} imgsStyle 图片的样式配置
 * @return React.ReactNode
 */
const useLazyImgs = (imgs: IImages[], imgsStyle?: React.CSSProperties) => {
    const allTarget = useMemo(() => {
        return imgs.reduce(
            (acc, img, index) => {
                const imgRef = React.createRef() as any;
                acc.refs.push(imgRef);
                acc.images.push(
                    <img
                        data-src={img?.src}
                        alt={img?.alt || ''}
                        key={img?.id || index}
                        style={imgsStyle}
                        ref={imgRef}
                    />
                );

                return acc;
            },
            {
                refs: [],
                images: [],
            } as {
                refs: Array<HTMLImageElement>;
                images: Array<JSX.Element>;
            }
        );
    }, []);

    const io = useMemo(() => {
        return new IntersectionObserver(
            (entries) => {
                entries.forEach((item) => {
                    if (item.isIntersecting) {
                        const img = item.target as HTMLImageElement;
                        img.src = img.dataset.src as string;
                        io.unobserve(img);
                    }
                });
            },
            {
                root: null,
            }
        );
    }, []);

    const onload = useCallback(() => {
        allTarget.refs.forEach((item) => io.observe((item as any).current));
    }, []);

    return (
        <Fragment>
            {allTarget.images}
            <img
                onError={onload}
                src=''
                alt=''
            />
        </Fragment>
    );
};

export default useLazyImgs;
